/*
    这里是一个个reducer函数 每个函数管理这一个状态
        参数 为状态 state action
*/
import { ACTION_SUCCESS, ACTION_ERROR,
    UPDATE_SUCCESS,UPDATE_ERROR,
    GET_USERLIST, GET_MSGLIST, RECEIVE_MSG,
    READMSG, LOGIN_MSGS, LOGIN_HOME
    } from './action-types'
import { combineReducers} from 'redux'
import { getRedirect} from '../utils/tools'

const initUser = {
    username: '',
    type: '',
    msg: '',
    redirectTo: ''
}

//此时  state 是一个对象
function user(state=initUser, action) {
    switch(action.type){
        case ACTION_SUCCESS:
            const { type, header} = action.data
            return {...action.data, redirectTo: getRedirect(type, header)}//这里可以用{...state, ...action.data}后面的会把前面覆盖掉
        case  ACTION_ERROR:
            return action.data
        case  UPDATE_SUCCESS:
            return {...action.data}
        case  UPDATE_ERROR:
            return {...state, ...action.data}
        case LOGIN_HOME:
            return  initUser
        default:
            return state
    }
}


/*
    此时这里是操作获取用户列表的状态  不是操作 user的状态
    因此这里要新定义一个函数 管理这个状态
 */

const initUserList = []

function userList(state=initUserList, action) {
    switch (action.type) {
        case GET_USERLIST:
            return action.data //注意这里是一个数组
        case LOGIN_HOME:
            return  initUserList
        default:
            return state
    }
}

//初始化状态
const initMsgList = {
    users: {},
    chatMsgs: [],
    readCountMsgs:0//这里是标记有多少条消息没有读取的
}

//在这里操作 用户的聊天信息
function getMsgList(state=initMsgList, action) {
    switch (action.type) {
        case GET_MSGLIST://此时的结构为data:{}users:{},chatMsgs:[]}
            const { users, chatMsgs, userid} = action.data
            /*
                在这里做总的未读消息
                     这里 是统计 发给我的 以及 reade为false的数量
             */
            return {
                users,
                chatMsgs,
                readCountMsgs: state.readCountMsgs + chatMsgs.reduce((prev, msg) => prev+(!msg.read && msg.to === userid?1:0), 0)
            }

        case LOGIN_MSGS:
            const userss = action.data.users
            return{...state, users: userss}

        case RECEIVE_MSG:
            // 此时上面已经取过 userid  这里不能在取 不然会报错
            // 可以统一在上面取 因为在同一个作用域 变量名不能相同(ES6)
            // const { chatMsg, userid} = action.data
            const { chatMsg} = action.data
            return{
                users: state.users,
                chatMsgs: [...state.chatMsgs, chatMsg],
                readCountMsgs: state.readCountMsgs + (!chatMsg.read && chatMsg.to === action.data.userid?1:0)
            }//此时应该只修改chatMsgs 其他不要动
        case READMSG:
            const { from, to, count} = action.data
            return{
                users: state.users,
                /*
                    此时这里把state的已读消息的read修改为true
                        但是此时你不能改变 state的数据  只能通过state返回一个新的状态
                        因此这里不能 提高 数组的 forEach()遍历数组 修改数据
                        因为该方法 是直接修改原数据  并不是返回一个新的数据

                            forEach()
                            state.chatMsgs.forEach((msg) => {
                                //这里的条件挺多
                                if (msg.from === from && msg.to === to && !msg.read) {
                                    msg.read = true
                                }
                            })

                            但是此时已经修改了原数据
                            下面使用 map()方法


                        因此这里使用数组的map(0方法
                        */

                chatMsgs: state.chatMsgs.map(msg =>{
                        //此时这里也要注意 因为是处理 别人发给我的消息
                        // 再别人发的消息中 后台存储的数据 to即为自己_id  from即为 它对方的_id注意
                        //注意处理自己的 消息 和别人的消息不一样
                        if (msg.from === to && msg.to === from && !msg.read) {
                            //此时也不能这样写 也是修改了原来数据
                            // 这也是修改了原数据 在返回 因此 使用 ...运算符
                            //return msg.read = true
                            return {...msg, read: true}//使用了这个是相当于复制了一份 msg
                                                    // 这里只是修改复制的那份 返回的是那分复制的那份
                        }else{
                            return msg
                        }
                    }),
                readCountMsgs: state.readCountMsgs - count
            }
        case LOGIN_HOME:
            return  initMsgList
        default:
            return state
    }
}


/*
    此时是暴漏多个 函数的状态 使用到了combineReducers
    这里里面 存放 一个对象 里面是 状态函数的 函数名即可
    要在  组件 拿到该对象 state.状态函数名即可
 */
export default combineReducers({
    user,
    userList,
    getMsgList
})

//此时状态的结构为 { user:{ },UserList:{ }}



